package com.xuyu.ddd.aggregate.core.aggregate;


import com.xuyu.ddd.aggregate.core.field.LazyAndPersistence;
import com.xuyu.ddd.aggregate.core.persistence.RepoUtil;
import org.apache.commons.lang3.SerializationUtils;

import java.io.Serializable;
import java.lang.reflect.Field;
import java.util.List;

/**
 * 聚合仓库，用于生成聚合
 */
public class AggregateFactory {

    /**
     * 用于生成可持久话的聚合， 对于LazyAndPersistence字段，需要特殊进行处理
     * @param t 聚合根
     * @return 聚合
     * @param <T> 聚合根类型
     * @throws IllegalAccessException 异常
     */

    @SuppressWarnings("unchecked")
    public static <T extends Serializable, R> Aggregate<T> buildAggregate(T t) throws IllegalAccessException {
        //获得快照对对象
        T rootSnapshot = SerializationUtils.clone(t);
        List<Field> allField = RepoUtil.getAllField(rootSnapshot.getClass());
        for (Field field : allField) {
            if (field.getType().equals(LazyAndPersistence.class)) {
                //快照的
                field.setAccessible(true);
                LazyAndPersistence<R> lazy = (LazyAndPersistence<R>)field.get(rootSnapshot);
                //原始的
                LazyAndPersistence<R> original = (LazyAndPersistence<R>)field.get(t);
                original.setSnapShot(lazy);
            }
        }
        return new Aggregate<T>()
                .setRoot(t)
                .setSnapShot(rootSnapshot);
    }


    /**
     * 用于第一次聚合的创建
     * @param t 聚合根
     * @return 聚合
     * @param <T> 聚合根类型
     */
    public static <T extends Serializable> Aggregate<T> buildAggregateWithOutSnapshot(T t) {
        return new Aggregate<T>()
                .setRoot(t);
    }


}
